import { EnvEnum } from "@/common/enums/env.enum";
import { RedisKeyEnum } from "@/common/enums/redis-key.enum";
import { StrategyEnum } from "@/common/enums/strategy.enum";
import { JwtPayloadInterface } from "@/common/interfaces";
import { RedisService } from "@/common/redis/redis.service";
import { HttpException, HttpStatus, Injectable } from "@nestjs/common";
import { ConfigService } from "@nestjs/config";
import { PassportStrategy } from "@nestjs/passport";
import { ExtractJwt, Strategy } from "passport-jwt";

@Injectable()
export class JwtAccessStrategy extends PassportStrategy(
	Strategy,
	StrategyEnum.JWT_ACCESS,
) {
	constructor(
		private readonly configService: ConfigService,
		private readonly redisService: RedisService,
	) {
		super({
			jwtFromRequest: ExtractJwt.fromAuthHeaderAsBearerToken(),
			secretOrKey: Buffer.from(
				configService.get<string>(EnvEnum.JWT_PUBLIC_KEY),
				"base64",
			).toString("utf-8"),
			algorithms: ["RS256"],
			passReqToCallback: true,
		});
	}

	async validate(req, payload): Promise<JwtPayloadInterface> {
		const headerToken = ExtractJwt.fromAuthHeaderAsBearerToken()(req);
		const redisToken = await this.redisService._get(
			RedisKeyEnum.LoginKey + payload.id,
		);

		if (headerToken !== redisToken) {
			throw new HttpException("其他地方登录", HttpStatus.FORBIDDEN);
		}
		return {
			id: payload.id,
			name: payload.name,
			email: payload.email,
		};
	}
}
